package tech.yixiyun.framework.kuafu.controller.action;


import tech.yixiyun.framework.kuafu.controller.interceptor.IControllerInterceptor;
import tech.yixiyun.framework.kuafu.controller.interceptor.InterceptorContext;
import tech.yixiyun.framework.kuafu.controller.request.KuafuRequest;
import tech.yixiyun.framework.kuafu.controller.response.KuafuResponse;
import tech.yixiyun.framework.kuafu.controller.route.RouteNode;
import tech.yixiyun.framework.kuafu.view.View;

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.Iterator;

/**
 * 负责Action调用流程的控制器
 */
public class ActionInvoker {

    private Action action;

    private Iterator<IControllerInterceptor> interceptorIterator;

    public ActionInvoker() {
        this.interceptorIterator = InterceptorContext.getInterceptorIterator();
    }

    public ActionInvoker(Action action) {
        this();
        this.action = action;
    }

    /**
     * 继续让后面的拦截器执行
     * @return
     */
    public View invoke() {
        View view = null;
        if (this.interceptorIterator.hasNext()) {
            view = this.interceptorIterator.next().intercept(this);
        } else {
            try {
                view =  action.execute();
            } catch (InvocationTargetException e) {
                Throwable exception = e.getTargetException();
                if (exception != null && exception instanceof RuntimeException ) {
                    throw (RuntimeException)exception;
                } else {
                    throw new RuntimeException(e);
                }
            } catch (IllegalAccessException e) {
                throw new RuntimeException(e);
            }
        }
        return view;
    }

    /**
     * 本次请求处理对象
     * @return
     */
    public Action getAction() {
        return this.action;
    }

    /**
     * 获取本次请求的路由对象
     * @return
     */
    public RouteNode getRoute() {
        return this.action.getRoute();
    }

    /**
     * 本次请求映射的url
     * @return
     */
    public String getRouteUrl() {
        return getRoute().getPath();
    }

    /**
     * 处理本次请求的方法
     * @return
     */
    public Method getActionMethod() {
        return getAction().getControllerMethod();
    }

    /**
     * 处理本次请求的Controller类
     * @return
     */
    public Class getActionController() {
        return getAction().getControllerClass();
    }

    /**
     * 处理本次请求的Controller类实例
     * @return
     */
    public Object getActionControllerInstance()  {
        return getAction().getControllerInstance();
    }

    /**
     * 获取本次请求对象
     * @return
     */
    public KuafuRequest getRequest() {
        return getAction().getRequest();
    }

    /**
     * 获取本次响应对象
     * @return
     */
    public KuafuResponse getResponse() {
        return getAction().getResponse();
    }



}
